package com.moon.utils;

import static org.apache.http.params.CoreConnectionPNames.CONNECTION_TIMEOUT;
import static org.apache.http.params.CoreConnectionPNames.SO_TIMEOUT;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.nio.charset.Charset;
import java.util.List;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.NameValuePair;
import org.apache.http.client.HttpClient;
import org.apache.http.client.ResponseHandler;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.mime.HttpMultipartMode;
import org.apache.http.entity.mime.MultipartEntity;
import org.apache.http.entity.mime.content.FileBody;
import org.apache.http.entity.mime.content.StringBody;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.params.HttpParams;
import org.apache.http.params.HttpProtocolParams;
import org.apache.http.protocol.HTTP;

import android.os.Build;
import android.util.Log;

/**
 * http工具类
 * 
 * @author paul
 * @date 2014年5月2日
 */
public class HttpClientUtils {

    private static final int               CONNECT_TIMEOUT = 1000;                                 //连接超时
    private static final int               SO_TIMEOUT_TIME = 3000;                                 //执行超时

    private static final String            TAG             = HttpClientUtils.class.getSimpleName();

    private static HttpClient              defaultClient   = new DefaultHttpClient();
    private static ResponseHandler<String> stringHandler   = new BasicResponseHandler();
    public static final String             USER_AGENT      = "moon ( " + Build.MODEL + "; android "
                                                                   + Build.VERSION.RELEASE + ")";
    static {
        HttpParams params = defaultClient.getParams();
        params.setIntParameter(CONNECTION_TIMEOUT, CONNECT_TIMEOUT);
        params.setIntParameter(SO_TIMEOUT, SO_TIMEOUT_TIME);
        // user-agent
        HttpProtocolParams.setUserAgent(params, USER_AGENT);
    }

    /**
     * @param url
     * @param params String[] 名值对,String[0]为key，String[1]为value
     * @return
     * @throws Exception
     */
    public static String post(String url, List<NameValuePair> params) throws Exception {
        return post(url, params, defaultClient);
    }

    /**
     * 带图片上传
     * 
     * @param url
     * @param params
     * @return
     * @throws Exception
     */
    public static String postWithImage(String url, List<NameValuePair> params) throws Exception {
        return postWithImage(url, params, defaultClient);
    }

    /**
     * 下载文件
     * 
     * @param url
     * @param toFileName
     * @throws IOException
     */
    public static InputStream download(final String url) throws Exception {
        return download(url, defaultClient);
    }

    /**
     * 下载文件
     * 
     * @param url
     * @param toFileName
     * @param client
     * @throws IOException
     * @throws
     */
    private static InputStream download(final String url, HttpClient client) throws Exception {
        HttpGet httpGet = new HttpGet(url);
        try {
            HttpResponse response;
            response = client.execute(httpGet);
            HttpEntity entity = response.getEntity();
            return entity.getContent();
        } catch (IOException e) {
            Log.e(TAG, e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            Log.e(TAG, e.getMessage(), e);
            httpGet.abort();
            throw new Exception(e.getMessage(), e);
        }

    }

    /**
     * 提交
     * 
     * @param url
     * @param params
     * @param client
     * @return
     * @throws Exception
     */
    private static String post(String url, List<NameValuePair> params, HttpClient client)
            throws Exception {
        HttpPost httpPost = new HttpPost(url);
        try {
            httpPost.setEntity(new UrlEncodedFormEntity(params, HTTP.UTF_8));
        } catch (UnsupportedEncodingException e) {
            Log.e(TAG, e.getMessage(), e);
            return null;
        }
        try {
            return client.execute(httpPost, stringHandler);
        } catch (IOException e) {
            Log.e(TAG, e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            Log.e(TAG, e.getMessage(), e);
            httpPost.abort();
            throw new Exception(e.getMessage(), e);
        }
    }

    /**
     * 带图片上传
     * 
     * @param url
     * @param params
     * @param client
     * @return
     * @throws Exception
     */
    private static String postWithImage(String url, List<NameValuePair> params, HttpClient client)
            throws Exception {
        HttpPost httpPost = new HttpPost(url);
        //        try {
        //            httpPost.setEntity(new UrlEncodedFormEntity(params, HTTP.UTF_8));
        //        } catch (UnsupportedEncodingException e) {
        //            Log.e(TAG, e.getMessage(), e);
        //            return null;
        //        }
        try {
            MultipartEntity entity = new MultipartEntity(HttpMultipartMode.BROWSER_COMPATIBLE);
            for (int index = 0; index < params.size(); index++) {
                if (params.get(index).getValue() == null) {
                    continue;
                }

                if (params.get(index).getName().contains("image")
                        || params.get(index).getName().contains("Image")) {
                    // If the key equals to "image", we use FileBody to transfer the data
                    entity.addPart(params.get(index).getName(),
                            new FileBody(new File(params.get(index).getValue())));
                } else {
                    // Normal string data
                    //Charset.forName("UTF-8") 解决服务器获取时乱码问题
                    entity.addPart(params.get(index).getName(), new StringBody(params.get(index)
                            .getValue(),Charset.forName("UTF-8")));
                    //                    entity.addPart(params.get(index).getName(), new StringBody(URLEncoder.encode(params.get(index)
                    //                            .getValue(), HTTP.UTF_8)));
                }
            }

            httpPost.setEntity(entity);
            return client.execute(httpPost, stringHandler);
        } catch (IOException e) {
            Log.e(TAG, e.getMessage(), e);
            throw e;
        } catch (Exception e) {
            Log.e(TAG, e.getMessage(), e);
            httpPost.abort();
            throw new Exception(e.getMessage(), e);
        }
    }

}
